/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.ejb.metier;

import com.ejb.persistence.*;
import com.ejb.persistence.User;
import java.util.HashMap;
import java.util.List;
import java.util.Iterator;
import javax.ejb.Stateless;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;

/**
 *
 * @author Wanted
 * Class used to manage orders
 * 
 */
@Stateless
public class OrderManagerBean implements IOrderManager {
   @PersistenceContext 
   private EntityManager em;
   
    /**
     * 
     * Add new order 
     * @param idUser 
     * @param listBook
     * @return boolean
     * 
     */
   @Override
   public boolean addOrder(Long idUser, HashMap<Long,Integer> listBook) {
        Book b ;
        Order ord = new Order();
        try {
            User u = em.find(User.class, idUser);          
            ord.setUser(u);
            ord.setState(OrderState.Validée);
            
            em.persist(ord);
            if(listBook != null) {
                for( Iterator ii = listBook.keySet().iterator(); ii.hasNext();) { 
                    Invoice inv = new Invoice();
                    Long idBook = (Long)ii.next();
                    b = em.find(Book.class, idBook);
                    int  Quantity = (int) listBook.get(idBook);
                    inv.setBook(b);
                    inv.setQuantity(Quantity);
                    inv.setOrders(ord);
                    em.persist(inv);
                }
                System.out.println();
            }
            
            return true;
        } catch (Exception e) {
            return false;
        }
   }
   
    /**
     * 
     * Change the state of an order
     * @param idOrder  
     * @param state
     * @return boolean
     * 
     */
    @Override
   public boolean setState(Long idOrder, OrderState state) {
        try {
            Order o = null;
            o = em.find(Order.class, idOrder);
            o.setState(state);
            o = em.merge(o);
            return true;
        } catch (Exception e) {
            return false;
        }
   }
   
    /**
     * 
     * Return all orders
     * @param idUser 
     * @param waiting
     * @return List<Order>
     * 
     */
    @Override
    public List<Order> getOrders(Long idUser, boolean waiting) {
        Query q;


        if(idUser != Long.MIN_VALUE){
            User user = em.find(User.class, idUser);
            em.refresh(user);           
            if (waiting){
                q = em.createNamedQuery("Order.getWaitingOrders");
                q.setParameter("state", OrderState.Envoyée);

            } else {
                q = em.createNamedQuery("Order.getOrdersByUser");
            }
        
            q.setParameter("user", user);
        } else {
            q = em.createNamedQuery("Order.getAllOrders");
        }
        
        List<Order> orders = q.getResultList();
        
        for (Order o : orders){
            em.refresh(o);
        }
        
      return orders;
    }
    
    /**
     * 
     * Return orders for one user and one state
     * @param idUser 
     * @param state
     * @return List<Order>
     * 
     */    
    @Override
    public List<Order> getOrdersByUserAndStates(long idUser, OrderState state) {
        User user = em.find(User.class, idUser);
        em.refresh(user);
        Query q;

        q = em.createNamedQuery("Order.getOrdersByUserAndState");
        q.setParameter("state", state);
        q.setParameter("user", user);

        List<Order> orders = q.getResultList();

        for (Order o : orders){
            em.refresh(o);
        }
        return orders;
    }
    
    /**
     * 
     * Return orders for one user and two state 
     * @param idUser 
     * @param state1
     * @param  state2
     * @return List<Order>
     * 
     */ 
    @Override
    public List<Order> getOrdersByUserAndTwoStates(long idUser, OrderState state1, OrderState state2) {
        User user = em.find(User.class, idUser);
        em.refresh(user);
        Query q;

        q = em.createNamedQuery("Order.getOrdersByUserAndTwoStates");
        q.setParameter("stateOne", state1);
        q.setParameter("stateTwo", state2);
        q.setParameter("user", user);

        List<Order> orders = q.getResultList();

        for (Order o : orders){
            em.refresh(o);
        }
        return orders;
    }

}
